/**
 *******************************************************************************
 * @FileName  : tlsr825x_gpio.h
 * @Author    : GaoQiu
 * @CreateDate: 2020-09-10
 * @Copyright : Copyright(C) GaoQiu
 *              All Rights Reserved.
 *
 *******************************************************************************
 *
 * The information contained herein is confidential and proprietary property of
 * GaoQiu and is available under the terms of Commercial License Agreement
 * between GaoQiu and the licensee in separate contract or the terms described
 * here-in.
 *
 * This heading MUST NOT be removed from this file.
 *
 * Licensees are granted free, non-transferable use of the information in this
 * file under Mutual Non-Disclosure Agreement. NO WARRENTY of ANY KIND is provided.
 *
 *******************************************************************************
 */
#ifndef TLSR825X_GPIO_H_
#define TLSR825X_GPIO_H_

#include "tlsr825x.h"

#define GPIO_MODE_AF_MASK    0x10
#define	GPIO_MODE_OUT_MASK   0x01

/*!  GPIO mode define. */
typedef enum{
	GPIO_Mode_In      = 0x00,
	GPIO_Mode_Out     = 0x01,
	GPIO_Mode_In_Out  = 0x02,
	GPIO_Mode_AF_In   = 0x10,
	GPIO_Mode_AF_Out  = 0x11,
}GPIOMode_Type_t;
#define IS_GPIO_MODE_VALID(MODE)  ((MODE) == GPIO_Mode_In     || \
		                           (MODE) == GPIO_Mode_Out    || \
		                           (MODE) == GPIO_Mode_In_Out || \
                                   (MODE) == GPIO_Mode_AF_In  || \
                                   (MODE) == GPIO_Mode_AF_Out   )

/*!  GPIO pull up/down define. */
typedef enum{
	GPIO_Pull_Floating = 0x00,   /*!< floating       */
	GPIO_PullUp_Weak   = 0x01,   /*!< pull up 10k    */
	GPIO_PullDown      = 0x02,   /*!< pull down 100K */
	GPIO_PullUp_Strong = 0x03,   /*!< pull up 1M     */
}GPIOPull_Type_t;
#define IS_GPIO_PULL_VALID(PULL)  ((PULL) == GPIO_Pull_Floating || \
                                   (PULL) == GPIO_PullUp_Weak   || \
                                   (PULL) == GPIO_PullDown      || \
                                   (PULL) == GPIO_PullUp_Strong    )
/*!  GPIO trigger level define. */
typedef enum{
	GPIO_Trigger_Rising  = 0x00,
	GPIO_Trigger_Falling = 0x01,
}GPIOTrigger_Type_t;
#define IS_GPIO_TRIGGER_VALID(TRIGGER)   ((TRIGGER) == GPIO_Trigger_Rising || \
		                                  (TRIGGER) == GPIO_Trigger_Falling   )

/*!  GPIO Wake up level define. */
typedef enum{
	GPIO_WakePol_Low  = 0x00,
	GPIO_WakePol_High = 0x01,
}GPIOWakePol_Type_t;


/*!  GPIO initialization type. */
typedef struct{
	uint16_t          GPIO_Pin;  /*!< GPIO pin.                   */
	GPIOMode_Type_t   GPIO_Mode; /*!< GPIO Input and Output mode. */
	GPIOPull_Type_t   GPIO_Pull; /*!< GPIO pull up/down.          */
}GPIO_InitType_t;

/*!  GPIOx define. */
#define IS_GPIO_GRP(GPIOx)   ((GPIOx) == GPIOA || (GPIOx) == GPIOB ||(GPIOx) == GPIOC ||(GPIOx) == GPIOD)

/************************* GPIO Pin *******************************************/
#define GPIO_GRP_MASK              ((uint16_t)(0x0300))

#define GPIOA_GRP                  ((uint16_t)(0x0000))
#define GPIOB_GRP                  ((uint16_t)(0x0100))
#define GPIOC_GRP                  ((uint16_t)(0x0200))
#define GPIOD_GRP                  ((uint16_t)(0x0300))

/******* GPIO_Pin_x define *****/

#define GPIO_Pin_0                 ((uint16_t)(0x0001))
#define GPIO_Pin_1                 ((uint16_t)(0x0002))
#define GPIO_Pin_2                 ((uint16_t)(0x0004))
#define GPIO_Pin_3                 ((uint16_t)(0x0008))
#define GPIO_Pin_4                 ((uint16_t)(0x0010))
#define GPIO_Pin_5                 ((uint16_t)(0x0020))
#define GPIO_Pin_6                 ((uint16_t)(0x0040))
#define GPIO_Pin_7                 ((uint16_t)(0x0080))
#define GPIO_Pin_All               ((uint16_t)(0x00FF))


/******* GPIO_Pn define ********/

/* GPIO_PAx */
#define GPIO_PA0                   (GPIOA_GRP + GPIO_Pin_0)
#define GPIO_PA1                   (GPIOA_GRP + GPIO_Pin_1)
#define GPIO_PA2                   (GPIOA_GRP + GPIO_Pin_2)
#define GPIO_PA3                   (GPIOA_GRP + GPIO_Pin_3)
#define GPIO_PA4                   (GPIOA_GRP + GPIO_Pin_4)
#define GPIO_PA5                   (GPIOA_GRP + GPIO_Pin_5)
#define GPIO_PA6                   (GPIOA_GRP + GPIO_Pin_6)
#define GPIO_PA7                   (GPIOA_GRP + GPIO_Pin_7)

/* GPIO_PBx */
#define GPIO_PB0                   (GPIOB_GRP + GPIO_Pin_0)
#define GPIO_PB1                   (GPIOB_GRP + GPIO_Pin_1)
#define GPIO_PB2                   (GPIOB_GRP + GPIO_Pin_2)
#define GPIO_PB3                   (GPIOB_GRP + GPIO_Pin_3)
#define GPIO_PB4                   (GPIOB_GRP + GPIO_Pin_4)
#define GPIO_PB5                   (GPIOB_GRP + GPIO_Pin_5)
#define GPIO_PB6                   (GPIOB_GRP + GPIO_Pin_6)
#define GPIO_PB7                   (GPIOB_GRP + GPIO_Pin_7)

/* GPIO_PCx */
#define GPIO_PC0                   (GPIOC_GRP + GPIO_Pin_0)
#define GPIO_PC1                   (GPIOC_GRP + GPIO_Pin_1)
#define GPIO_PC2                   (GPIOC_GRP + GPIO_Pin_2)
#define GPIO_PC3                   (GPIOC_GRP + GPIO_Pin_3)
#define GPIO_PC4                   (GPIOC_GRP + GPIO_Pin_4)
#define GPIO_PC5                   (GPIOC_GRP + GPIO_Pin_5)
#define GPIO_PC6                   (GPIOC_GRP + GPIO_Pin_6)
#define GPIO_PC7                   (GPIOC_GRP + GPIO_Pin_7)

/* GPIO_PDx */
#define GPIO_PD0                   (GPIOD_GRP + GPIO_Pin_0)
#define GPIO_PD1                   (GPIOD_GRP + GPIO_Pin_1)
#define GPIO_PD2                   (GPIOD_GRP + GPIO_Pin_2)
#define GPIO_PD3                   (GPIOD_GRP + GPIO_Pin_3)
#define GPIO_PD4                   (GPIOD_GRP + GPIO_Pin_4)
#define GPIO_PD5                   (GPIOD_GRP + GPIO_Pin_5)
#define GPIO_PD6                   (GPIOD_GRP + GPIO_Pin_6)
#define GPIO_PD7                   (GPIOD_GRP + GPIO_Pin_7)


/********************* GPIO Alternative Function ******************************/

/************ GPIO_AF_x define *************/

#define GPIO_AF_NONE            0
#define GPIO_AF_SPI             1
#define GPIO_AF_IIC             2
#define GPIO_AF_UART            3
#define GPIO_AF_DMIC            4
#define GPIO_AF_PWM0            5
#define GPIO_AF_PWM1            6
#define GPIO_AF_PWM2            7
#define GPIO_AF_PWM3            8
#define GPIO_AF_PWM4            9
#define GPIO_AF_PWM5            10
#define GPIO_AF_PWM0_N          11
#define GPIO_AF_PWM1_N          12
#define GPIO_AF_PWM2_N          13
#define GPIO_AF_PWM3_N          14
#define GPIO_AF_PWM4_N          15
#define GPIO_AF_PWM5_N          16
#define GPIO_AF_USB             17
#define GPIO_AF_SDM             18
#define GPIO_AF_IIS             19
#define GPIO_AF_SWS             20
#define GPIO_AF_SWM             21


/********** GPIO_AF_Remap define **********/

#define GPIOA3_AF_Remap_SPI_IN   ((uint16_t)(GPIOA3_AF_SPI_IN))
#define GPIOA3_AF_Remap_SPI_OUT  ((uint16_t)(GPIOA3_AF_SPI_IIC_OUT))
#define GPIOA3_AF_Remap_IIC_IN   ((uint16_t)(GPIOA3_AF_IIC_IN))
#define GPIOA3_AF_Remap_IIC_OUT  ((uint16_t)(GPIOA3_AF_SPI_IIC_OUT))

#define GPIOA4_AF_Remap_SPI_IN   ((uint16_t)(GPIOA4_AF_SPI_IN))
#define GPIOA4_AF_Remap_SPI_OUT  ((uint16_t)(GPIOA4_AF_SPI_IIC_OUT))
#define GPIOA4_AF_Remap_IIC_IN   ((uint16_t)(GPIOA4_AF_IIC_IN))
#define GPIOA4_AF_Remap_IIC_OUT  ((uint16_t)(GPIOA4_AF_SPI_IIC_OUT))

#define GPIOB6_AF_Remap_SPI_IN   ((uint16_t)(GPIOB6_AF_SPI_IN))
#define GPIOB6_AF_Remap_SPI_OUT  ((uint16_t)(GPIOB6_AF_SPI_IIC_OUT))
#define GPIOB6_AF_Remap_IIC_IN   ((uint16_t)(GPIOB6_AF_IIC_IN))
#define GPIOB6_AF_Remap_IIC_OUT  ((uint16_t)(GPIOB6_AF_SPI_IIC_OUT))

#define GPIOD7_AF_Remap_SPI_IN   ((uint16_t)(GPIOD7_AF_SPI_IN))
#define GPIOD7_AF_Remap_SPI_OUT  ((uint16_t)(GPIOD7_AF_SPI_IIC_OUT))
#define GPIOD7_AF_Remap_IIC_IN   ((uint16_t)(GPIOD7_AF_IIC_IN))
#define GPIOD7_AF_Remap_IIC_OUT  ((uint16_t)(GPIOD7_AF_SPI_IIC_OUT))


void GPIO_DefInit(void);

void GPIO_Init(GPIO_Type_t *GPIOx, GPIO_InitType_t *GPIO_InitStruct);
void GPIO_SetAlternFunc(GPIO_Type_t *GPIOx, uint16_t GPIO_Pin, uint16_t GPIO_AFunc);
void GPIO_RemapAlternFunc(GPIO_Type_t *GPIOx, uint16_t GPIO_Pin, uint16_t GPIO_AF_Remap);
void GPIO_SetPullMode(GPIO_Type_t *GPIOx, uint16_t GPIO_Pin, GPIOPull_Type_t GPIO_Pull);

uint8_t GPIO_ReadInputBit(GPIO_Type_t *GPIOx, uint16_t GPIO_Pin);
uint8_t GPIO_ReadOutputBit(GPIO_Type_t *GPIOx, uint16_t GPIO_Pin);
void    GPIO_WriteBits(GPIO_Type_t *GPIOx, uint16_t GPIO_Pin, bool_t bitValue);
void    GPIO_ToggleBits(GPIO_Type_t *GPIOx, uint16_t GPIO_Pin);
uint8_t GPIO_ReadOutputData(GPIO_Type_t *GPIOx);
uint8_t GPIO_ReadInputData(GPIO_Type_t *GPIOx);
void    GPIO_Write(GPIO_Type_t *GPIOx, uint8_t value);

void GPIO_ITConfig(GPIO_Type_t *GPIOx, uint16_t GPIO_Pin, GPIOTrigger_Type_t GPIO_Trigger, bool_t enable);
void GPIO_IT_Enable(void);
void GPIO_IT_Disable(void);
uint8_t GPIO_GetState(GPIO_Type_t *GPIOx, uint16_t GPIO_Pin);

/*!  GPIO wake pin */
void GPIO_SetWakeup(GPIO_Type_t *GPIOx, uint16_t GPIO_Pin, GPIOWakePol_Type_t wakePol, bool_t enable);


/*******************************************************************************
 *
 *  This set of APIs can also be used. It is designed for use in special situations.
 *
 ******************************************************************************/
#define GPIO_GRP_ID(x)            ((uint8_t)((x)>>8))
#define GPIO_PIN_MASK(x)          ((uint8_t)(x) & 0xFF)

void GPIO_InitEx(uint16_t GPIO_Pn, GPIOMode_Type_t GPIO_Mode);
void GPIO_SetAlternFuncEx(uint16_t GPIO_Pn, uint16_t GPIO_AFunc);
void GPIO_RemapAlternFuncEx(uint16_t GPIO_Pn, uint16_t GPIO_AF_Remap);
void GPIO_SetPullModeEx(uint16_t GPIO_Pn, GPIOPull_Type_t GPIO_Pull);
uint8_t GPIO_ReadInputBitEx(uint16_t GPIO_Pn);
uint8_t GPIO_ReadOutputBitEx(uint16_t GPIO_Pn);
void GPIO_WriteBitsEx(uint16_t GPIO_Pn, bool_t bitValue);
void GPIO_ToggleBitsEx(uint16_t GPIO_Pn);
void GPIO_ITConfigEx(uint16_t GPIO_Pn, GPIOTrigger_Type_t GPIO_Trigger, bool_t enable);
uint8_t GPIO_GetStateEx(uint16_t GPIO_Pn);

void GPIO_SetWakeupEx(uint16_t GPIO_Pn, GPIOWakePol_Type_t wakePol, bool_t enable);

#endif /* TLSR825X_GPIO_H_ */
